package com.webuy.h5.container

import android.os.Build
import android.text.TextUtils
import com.tencent.smtt.sdk.MimeTypeMap
import com.tencent.smtt.export.external.interfaces.WebResourceResponse
import okhttp3.Request
import timber.log.Timber
import java.util.*


/**
 * author: luoXiong
 * e-mail: 382060748@qq.com
 * date: 2021/7/22 11:06
 * version: 1.0
 * desc:
 */
object OkHttpCacheManager {
    private var allCount = 0
    private var cacheCount = 0

    //    private val mHttpClient: OkHttpClient
    private val TAG = "OkHttpCacheManager"

    //只缓存白名单中的资源
    private val CACHE_MIME_TYPE = object : HashSet<String>() {
        init {
            add("html")
            add("htm")
            add("js")
            add("ico")
            add("css")
            add("png")
            add("jpg")
            add("jpeg")
            add("gif")
            add("bmp")
            add("ttf")
            add("woff")
            add("woff2")
            add("otf")
            add("eot")
            add("svg")
            add("xml")
            add("swf")
            add("txt")
            add("text")
            add("conf")
            add("webp")
        }
    }


    /**
     * 针对url级别的缓存，包括主文档，图片，js，css等
     *
     * @param url
     * @param headers
     * @return
     */
    fun interceptRequest(url: String, headers: Map<String?, String?>?): WebResourceResponse? {
        val okHttpClient = JlH5Container.getOkHttpClient() ?: return null
        try {
            val extension = MimeTypeMap.getFileExtensionFromUrl(url)
            if (TextUtils.isEmpty(extension) || !CACHE_MIME_TYPE.contains(extension.lowercase(Locale.getDefault()))) {
                //不在支持的缓存范围内
                Timber.d("不在支持的缓存范围内url:$url  extension=$extension")
                return null
            }
            val startTime = System.currentTimeMillis()
            val reqBuilder: Request.Builder = Request.Builder().url(url)
            if (headers != null) {
                for ((key, value) in headers) {
                    reqBuilder.addHeader(key!!, value!!)
                }
            }
            val request: Request = reqBuilder.get().build()
            val response = okHttpClient.newCall(request).execute()
            if (response.code != 200) {
                Timber.d("响应码 = " + response.code + ",extension = " + extension)
                return null
            }
            //  String mimeType = MimeTypeMapUtils.getMimeTypeFromUrl(url);

            val mimeType: String = MimeTypeMap.getFileExtensionFromUrl(url)
            Timber.d("mimeType = $mimeType,extension = $extension,url = $url")
            val encode = "UTF-8"
            // val okHttpWebResourceResponse = WebResourceResponse(mimeType, "", response.body!!.byteStream())
            val body = response.body!!


            val okHttpWebResourceResponse = WebResourceResponse(
                mimeType,
                encode,
                body.byteStream()
            )
            val cacheRes = response.cacheResponse
            val endTime = System.currentTimeMillis()
            val costTime = endTime - startTime
            allCount++
            if (cacheRes != null) {
                cacheCount++
                Timber.d(String.format("count rate = (%s),costTime = (%s);from cache: %s", 1.0f * cacheCount / allCount, costTime, url))
            } else {
                Timber.d(String.format("costTime = (%s);from server: %s", costTime, url))
            }
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
                var message = response.message
                if (TextUtils.isEmpty(message)) {
                    message = "OK"
                }
                try {
                    okHttpWebResourceResponse.setStatusCodeAndReasonPhrase(response.code, message)
                } catch (e: Exception) {
                    return null
                }
                val stringListMap: Map<String, List<String>?> = response.headers.toMultimap()
                val header: MutableMap<String, String> = HashMap()
                for ((key, value) in stringListMap) {
                    if (value != null && !value.isEmpty()) {
                        header[key] = value[0]
                    }
                }
                header.put("content-type", body.contentType()!!.type)
                header.put("content-encoding", "utf-8")
                //    Map<String, String> header = MimeTypeMap.multimapToSingle(response.headers().toMultimap());
                okHttpWebResourceResponse.responseHeaders = header
            }
            return okHttpWebResourceResponse
        } catch (t: Throwable) {
            t.printStackTrace()
        }
        return null
    }

}